import { Module } from "@nestjs/common";
import { TypeOrmModule } from "@nestjs/typeorm";
import { LogsService } from "./logs.service";
import { LogsController } from "./logs.controller";
import { Logs } from "./logs.entity";
// import { UserModule } from "../user/user.module"; // 移除循环依赖
import { WinstonModule, WinstonModuleOptions } from "nest-winston";
import { ConfigService } from "@nestjs/config";
import { SimpleLoggerService } from "./simple-logger.service";
import winston from "winston";
import * as path from "path";
import * as fs from "fs";
import { ConfigEnum } from "../enum/config.enum";

/**
 * 日志模块 (LogsModule)
 *
 * 负责管理系统日志相关的功能，包括：
 * - 日志记录和查询
 * - 用户操作审计
 * - 系统监控数据
 * - Winston文件日志集成
 * - 数据库日志存储
 */
@Module({
  imports: [
    // 注册 Logs 实体到 TypeORM
    TypeOrmModule.forFeature([Logs]),
    // UserModule, // 移除循环依赖 - UserService将直接注入LogsService
    // 配置Winston日志模块 - 集成winston.config.ts的配置
    WinstonModule.forRootAsync({
      inject: [ConfigService],
      useFactory: (configService: ConfigService) => {
        // 确保logs目录存在
        const logDir = path.join(process.cwd(), "logs");
        if (!fs.existsSync(logDir)) {
          fs.mkdirSync(logDir, { recursive: true });
        }

        const isDevelopment = configService.get("NODE_ENV") === "development";
        const logLevel = configService.get(ConfigEnum.LOG_LEVEL) || "info";

        return {
          level: logLevel,
          transports: [
            // 控制台输出 - 开发环境使用彩色格式
            new winston.transports.Console({
              format: winston.format.combine(
                winston.format.timestamp({
                  format: "YYYY-MM-DD HH:mm:ss",
                }),
                winston.format.errors({ stack: true }),
                winston.format.splat(),
                ...(isDevelopment
                  ? [
                      winston.format.colorize({ all: true }),
                      winston.format.printf(({ timestamp, level, message, context, stack, ...meta }) => {
                        const levelConfig = {
                          error: { icon: "❌", border: "═══════════════════════════════════════" },
                          warn: { icon: "⚠️ ", border: "───────────────────────────────────────" },
                          info: { icon: "📝", border: "┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈┈" },
                          debug: { icon: "🔍", border: "┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄" },
                          verbose: { icon: "💬", border: "⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯⋯" },
                        };

                        const cleanLevel = level.replace(/\x1b\[[0-9;]*m/g, "");
                        const config = levelConfig[cleanLevel] || {
                          icon: "📋",
                          border: "·········································",
                        };
                        // 确定日志来源
                        let source = "[NestWinston]";
                        if (context && typeof context === "string") {
                          if (context.includes("Service") || context.includes("Controller")) {
                            source = `[${context}]`;
                          } else if (
                            context === "HTTP" ||
                            context === "RouterExplorer" ||
                            context === "RoutesResolver"
                          ) {
                            source = "[Nest]";
                          } else if (context === "InstanceLoader" || context === "NestFactory") {
                            source = "[Nest]";
                          } else {
                            source = `[${context}]`;
                          }
                        }

                        // 基础日志格式 - 更美观的布局，在最前方显示来源（黄色）
                        let logMessage = `\n${config.border}\n\x1b[33m${source}\x1b[0m ${config.icon} ${timestamp} | ${level} | ${message}`;

                        const filteredMeta = { ...meta };
                        delete filteredMeta.timestamp;
                        delete filteredMeta.level;
                        delete filteredMeta.message;

                        // 只显示 meta 字段中的信息，简化日志输出
                        if (filteredMeta.meta && Object.keys(filteredMeta.meta).length > 0) {
                          logMessage += `\nwinston-logger.service：📊 详细信息:\n${JSON.stringify(
                            filteredMeta.meta,
                            null,
                            2,
                          )
                            .split("\n")
                            .map((line) => `   ${line}`)
                            .join("\n")}`;
                        }

                        if (stack && typeof stack === "string") {
                          logMessage += `\n🔥 错误堆栈:\n${stack
                            .split("\n")
                            .map((line) => `   ${line}`)
                            .join("\n")}`;
                        }

                        logMessage += `\n${config.border}\n`;
                        return logMessage;
                      }),
                    ]
                  : [winston.format.json()]),
              ),
            }),
            // 错误日志文件
            new winston.transports.File({
              filename: path.join(logDir, "error.log"),
              level: "error",
              format: winston.format.combine(
                winston.format.timestamp({ format: "YYYY-MM-DD HH:mm:ss" }),
                winston.format.errors({ stack: true }),
                winston.format.json(),
              ),
              maxsize: 5242880, // 5MB
              maxFiles: 5,
            }),
            // 组合日志文件（所有级别）
            new winston.transports.File({
              filename: path.join(logDir, "combined.log"),
              format: winston.format.combine(
                winston.format.timestamp({ format: "YYYY-MM-DD HH:mm:ss" }),
                winston.format.errors({ stack: true }),
                winston.format.json(),
              ),
              maxsize: 5242880, // 5MB
              maxFiles: 5,
            }),
            // 应用日志文件（info及以上级别）
            new winston.transports.File({
              filename: path.join(logDir, "app.log"),
              level: "info",
              format: winston.format.combine(
                winston.format.timestamp({ format: "YYYY-MM-DD HH:mm:ss" }),
                winston.format.printf(({ timestamp, level, message, context, stack }) => {
                  const logMessage = `${timestamp} [${level.toUpperCase()}] ${context ? `[${context}] ` : ""}${message}`;
                  return stack && typeof stack === "string" ? `${logMessage}\n${stack}` : logMessage;
                }),
              ),
              maxsize: 5242880, // 5MB
              maxFiles: 5,
            }),
          ],
          // 添加异常处理
          exceptionHandlers: [
            new winston.transports.Console({
              format: winston.format.combine(
                winston.format.timestamp(),
                winston.format.errors({ stack: true }),
                winston.format.printf(({ timestamp, message, stack }) => {
                  return `\n🚨🚨🚨 未捕获异常 🚨🚨🚨\n时间: ${timestamp}\n消息: ${message}\n堆栈:\n${stack && typeof stack === "string" ? stack : "无堆栈信息"}\n🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨\n`;
                }),
              ),
            }),
            new winston.transports.File({
              filename: path.join(logDir, "exceptions.log"),
              format: winston.format.combine(
                winston.format.timestamp({ format: "YYYY-MM-DD HH:mm:ss" }),
                winston.format.errors({ stack: true }),
                winston.format.json(),
              ),
            }),
          ],
          rejectionHandlers: [
            new winston.transports.Console({
              format: winston.format.combine(
                winston.format.timestamp(),
                winston.format.errors({ stack: true }),
                winston.format.printf(({ timestamp, message, stack }) => {
                  return `\n💥💥💥 未处理的Promise拒绝 💥💥💥\n时间: ${timestamp}\n消息: ${message}\n堆栈:\n${stack && typeof stack === "string" ? stack : "无堆栈信息"}\n💥💥💥💥💥💥💥💥💥💥💥💥💥💥💥💥💥💥\n`;
                }),
              ),
            }),
            new winston.transports.File({
              filename: path.join(logDir, "rejections.log"),
              format: winston.format.combine(
                winston.format.timestamp({ format: "YYYY-MM-DD HH:mm:ss" }),
                winston.format.errors({ stack: true }),
                winston.format.json(),
              ),
            }),
          ],
        } as WinstonModuleOptions;
      },
    }),
  ],
  controllers: [LogsController],
  providers: [LogsService, SimpleLoggerService],
  exports: [LogsService, SimpleLoggerService, WinstonModule], // 导出服务和Winston模块供其他模块使用
})
export class LogsModule {}
